package com.googlewell.zelix.tool;

import me.coley.recaf.search.*;
import me.coley.recaf.workspace.Workspace;

import java.util.Collection;
import java.util.List;

public class SearchTool {

    /**
     * 查询成员(包括成员变量和成员函数)定义(声明),所有者、名称、描述都可空,但不能同时为空
     *
     * @param workspace  工作区
     * @param owner      所有者
     * @param name       名称
     * @param desc       描述,如果是函数,函数参数和返回值有一项匹配即可.比如(Ljava/lang/Object;)Ljava/lang/Object;,我们可以Object进行搜索，不必给出完整描述.
     * @param stringMode 匹配模式
     * @param skipped    跳过的包
     * @return
     */
    public static SearchCollector searchMemberDefinition(Workspace workspace, String owner, String name, String desc, StringMatchMode stringMode, Collection<String> skipped) {
        return SearchBuilder.in(workspace)
                .skipDebug()
                .skipCode()
                .query(new MemberDefinitionQuery(owner, name, desc, stringMode))
                .skipPackages(skipped)
                .build();
    }

    /**
     * 查询类引用查询
     *
     * @param workspace  工作区
     * @param name       名称
     * @param stringMode 匹配模式
     * @param skipped    跳过的包
     * @return
     */
    public static SearchCollector searchClassReference(Workspace workspace, String name, StringMatchMode stringMode, Collection<String> skipped) {
        return SearchBuilder.in(workspace)
                .query(new ClassReferenceQuery(name, stringMode))
                .skipPackages(skipped)
                .build();
    }

    /**
     * 查询成员引用
     *
     * @param workspace  工作区
     * @param owner      所有者
     * @param name       名称
     * @param desc       描述
     * @param stringMode 匹配模式
     * @param skipped    跳过的包
     * @return
     */
    public static SearchCollector searchMemberReference(Workspace workspace, String owner, String name, String desc, StringMatchMode stringMode, Collection<String> skipped) {
        return SearchBuilder.in(workspace)
                .query(new MemberReferenceQuery(owner, name, desc, stringMode))
                .skipPackages(skipped)
                .build();
    }

    /**
     * 查询字符串
     *
     * @param workspace  工作区
     * @param pattern    搜索的字符串
     * @param stringMode 匹配模式
     * @param skipped    跳过的包
     * @return
     */
    public static SearchCollector searchString(Workspace workspace, String pattern, StringMatchMode stringMode, Collection<String> skipped) {
        return SearchBuilder.in(workspace)
                .skipDebug()
                .query(new StringQuery(pattern, stringMode))
                .skipPackages(skipped)
                .build();
    }

    /**
     * 查询值
     *
     * @param workspace 工作区
     * @param value     数值.后缀D/F/L为double/float/long
     * @param skipped   跳过的包
     * @return
     */
    public static SearchCollector searchValue(Workspace workspace, Object value, Collection<String> skipped) {
        return SearchBuilder.in(workspace)
                .skipDebug()
                .skipPackages(skipped)
                .query(new ValueQuery(value))
                .build();
    }

    /**
     * 查询指令文本
     *
     * @param workspace  工作区
     * @param lines      指令需要大写,支持多行搜索,搜索尽量不要变量,不同字节码工具的变量名不一
     * @param stringMode 匹配模式,根据匹配模式,指令不一定完整
     * @param skipped    跳过的包
     * @return
     */
    public static SearchCollector searchInsn(Workspace workspace, List<String> lines, StringMatchMode stringMode, Collection<String> skipped) {
        return SearchBuilder.in(workspace)
                .skipPackages(skipped)
                .query(new InsnTextQuery(lines, stringMode))
                .build();
    }

}
